home *** CD-ROM | disk | FTP | other *** search
/ Clickx 115 / Clickx 115.iso / software / tools / windows / tails-i386-0.16.iso / live / filesystem.squashfs / usr / lib / iceweasel / components / nsSessionStartup.js < prev    next >
Encoding:
JavaScript  |  2013-01-09  |  9.9 KB  |  289 lines

  1. /* 
  2. //@line 38 "/tmp/buildd/iceweasel-10.0.12esr/browser/components/sessionstore/src/nsSessionStartup.js"
  3. */
  4.  
  5. /**
  6. //@line 65 "/tmp/buildd/iceweasel-10.0.12esr/browser/components/sessionstore/src/nsSessionStartup.js"
  7. */
  8.  
  9. /* :::::::: Constants and Helpers ::::::::::::::: */
  10.  
  11. const Cc = Components.classes;
  12. const Ci = Components.interfaces;
  13. const Cr = Components.results;
  14. const Cu = Components.utils;
  15. Cu.import("resource://gre/modules/XPCOMUtils.jsm");
  16. Cu.import("resource://gre/modules/Services.jsm");
  17.  
  18. const STATE_RUNNING_STR = "running";
  19. const MAX_FILE_SIZE = 100 * 1024 * 1024; // 100 megabytes
  20.  
  21. function debug(aMsg) {
  22.   aMsg = ("SessionStartup: " + aMsg).replace(/\S{80}/g, "$&\n");
  23.   Services.console.logStringMessage(aMsg);
  24. }
  25.  
  26. /* :::::::: The Service ::::::::::::::: */
  27.  
  28. function SessionStartup() {
  29. }
  30.  
  31. SessionStartup.prototype = {
  32.  
  33.   // the state to restore at startup
  34.   _initialState: null,
  35.   _sessionType: Ci.nsISessionStartup.NO_SESSION,
  36.  
  37. /* ........ Global Event Handlers .............. */
  38.  
  39.   /**
  40.    * Initialize the component
  41.    */
  42.   init: function sss_init() {
  43.     // do not need to initialize anything in auto-started private browsing sessions
  44.     let pbs = Cc["@mozilla.org/privatebrowsing;1"].
  45.               getService(Ci.nsIPrivateBrowsingService);
  46.     if (pbs.autoStarted || pbs.lastChangedByCommandLine)
  47.       return;
  48.  
  49.     let prefBranch = Cc["@mozilla.org/preferences-service;1"].
  50.                      getService(Ci.nsIPrefService).getBranch("browser.");
  51.  
  52.     // get file references
  53.     var dirService = Cc["@mozilla.org/file/directory_service;1"].
  54.                      getService(Ci.nsIProperties);
  55.     let sessionFile = dirService.get("ProfD", Ci.nsILocalFile);
  56.     sessionFile.append("sessionstore.js");
  57.  
  58.     let doResumeSessionOnce = prefBranch.getBoolPref("sessionstore.resume_session_once");
  59.     let doResumeSession = doResumeSessionOnce ||
  60.                           prefBranch.getIntPref("startup.page") == 3;
  61.  
  62.     // only continue if the session file exists
  63.     if (!sessionFile.exists())
  64.       return;
  65.  
  66.     // get string containing session state
  67.     let iniString = this._readStateFile(sessionFile);
  68.     if (!iniString)
  69.       return;
  70.  
  71.     // parse the session state into a JS object
  72.     try {
  73.       // remove unneeded braces (added for compatibility with Firefox 2.0 and 3.0)
  74.       if (iniString.charAt(0) == '(')
  75.         iniString = iniString.slice(1, -1);
  76.       try {
  77.         this._initialState = JSON.parse(iniString);
  78.       }
  79.       catch (exJSON) {
  80.         var s = new Cu.Sandbox("about:blank", {sandboxName: 'nsSessionStartup'});
  81.         this._initialState = Cu.evalInSandbox("(" + iniString + ")", s);
  82.       }
  83.  
  84.       // If this is a normal restore then throw away any previous session
  85.       if (!doResumeSessionOnce)
  86.         delete this._initialState.lastSessionState;
  87.     }
  88.     catch (ex) { debug("The session file is invalid: " + ex); }
  89.  
  90.     let resumeFromCrash = prefBranch.getBoolPref("sessionstore.resume_from_crash");
  91.     let lastSessionCrashed =
  92.       this._initialState && this._initialState.session &&
  93.       this._initialState.session.state &&
  94.       this._initialState.session.state == STATE_RUNNING_STR;
  95.  
  96.     // Report shutdown success via telemetry. Shortcoming here are
  97.     // being-killed-by-OS-shutdown-logic, shutdown freezing after
  98.     // session restore was written, etc.
  99.     let Telemetry = Cc["@mozilla.org/base/telemetry;1"].getService(Ci.nsITelemetry);
  100.     Telemetry.getHistogramById("SHUTDOWN_OK").add(!lastSessionCrashed);
  101.  
  102.     // set the startup type
  103.     if (lastSessionCrashed && resumeFromCrash)
  104.       this._sessionType = Ci.nsISessionStartup.RECOVER_SESSION;
  105.     else if (!lastSessionCrashed && doResumeSession)
  106.       this._sessionType = Ci.nsISessionStartup.RESUME_SESSION;
  107.     else if (this._initialState)
  108.       this._sessionType = Ci.nsISessionStartup.DEFER_SESSION;
  109.     else
  110.       this._initialState = null; // reset the state
  111.  
  112.     // wait for the first browser window to open
  113.     // Don't reset the initial window's default args (i.e. the home page(s))
  114.     // if all stored tabs are pinned.
  115.     if (this.doRestore() &&
  116.         (!this._initialState.windows ||
  117.         !this._initialState.windows.every(function (win)
  118.            win.tabs.every(function (tab) tab.pinned))))
  119.       Services.obs.addObserver(this, "domwindowopened", true);
  120.  
  121.     Services.obs.addObserver(this, "sessionstore-windows-restored", true);
  122.  
  123.     if (this._sessionType != Ci.nsISessionStartup.NO_SESSION)
  124.       Services.obs.addObserver(this, "browser:purge-session-history", true);
  125.   },
  126.  
  127.   /**
  128.    * Handle notifications
  129.    */
  130.   observe: function sss_observe(aSubject, aTopic, aData) {
  131.     switch (aTopic) {
  132.     case "app-startup": 
  133.       Services.obs.addObserver(this, "final-ui-startup", true);
  134.       Services.obs.addObserver(this, "quit-application", true);
  135.       break;
  136.     case "final-ui-startup": 
  137.       Services.obs.removeObserver(this, "final-ui-startup");
  138.       Services.obs.removeObserver(this, "quit-application");
  139.       this.init();
  140.       break;
  141.     case "quit-application":
  142.       // no reason for initializing at this point (cf. bug 409115)
  143.       Services.obs.removeObserver(this, "final-ui-startup");
  144.       Services.obs.removeObserver(this, "quit-application");
  145.       if (this._sessionType != Ci.nsISessionStartup.NO_SESSION)
  146.         Services.obs.removeObserver(this, "browser:purge-session-history");
  147.       break;
  148.     case "domwindowopened":
  149.       var window = aSubject;
  150.       var self = this;
  151.       window.addEventListener("load", function() {
  152.         self._onWindowOpened(window);
  153.         window.removeEventListener("load", arguments.callee, false);
  154.       }, false);
  155.       break;
  156.     case "sessionstore-windows-restored":
  157.       Services.obs.removeObserver(this, "sessionstore-windows-restored");
  158.       // free _initialState after nsSessionStore is done with it
  159.       this._initialState = null;
  160.       break;
  161.     case "browser:purge-session-history":
  162.       Services.obs.removeObserver(this, "browser:purge-session-history");
  163.       // reset all state on sanitization
  164.       this._sessionType = Ci.nsISessionStartup.NO_SESSION;
  165.       break;
  166.     }
  167.   },
  168.  
  169.   /**
  170.    * Removes the default arguments from the first browser window
  171.    * (and removes the "domwindowopened" observer afterwards).
  172.    */
  173.   _onWindowOpened: function sss_onWindowOpened(aWindow) {
  174.     var wType = aWindow.document.documentElement.getAttribute("windowtype");
  175.     if (wType != "navigator:browser")
  176.       return;
  177.     
  178.     /**
  179.      * Note: this relies on the fact that nsBrowserContentHandler will return
  180.      * a different value the first time its getter is called after an update,
  181.      * due to its needHomePageOverride() logic. We don't want to remove the
  182.      * default arguments in the update case, since they include the "What's
  183.      * New" page.
  184.      *
  185.      * Since we're garanteed to be at least the second caller of defaultArgs
  186.      * (nsBrowserContentHandler calls it to determine which arguments to pass
  187.      * at startup), we know that if the window's arguments don't match the
  188.      * current defaultArguments, we're either in the update case, or we're
  189.      * launching a non-default browser window, so we shouldn't remove the
  190.      * window's arguments.
  191.      */
  192.     var defaultArgs = Cc["@mozilla.org/browser/clh;1"].
  193.                       getService(Ci.nsIBrowserHandler).defaultArgs;
  194.     if (aWindow.arguments && aWindow.arguments[0] &&
  195.         aWindow.arguments[0] == defaultArgs)
  196.       aWindow.arguments[0] = null;
  197.  
  198.     try {
  199.       Services.obs.removeObserver(this, "domwindowopened");
  200.     } catch (e) {
  201.       // This might throw if we're removing the observer multiple times,
  202.       // but this is safe to ignore.
  203.     }
  204.   },
  205.  
  206. /* ........ Public API ................*/
  207.  
  208.   /**
  209.    * Get the session state as a jsval
  210.    */
  211.   get state() {
  212.     return this._initialState;
  213.   },
  214.  
  215.   /**
  216.    * Determine whether there is a pending session restore.
  217.    * @returns bool
  218.    */
  219.   doRestore: function sss_doRestore() {
  220.     return this._sessionType == Ci.nsISessionStartup.RECOVER_SESSION ||
  221.            this._sessionType == Ci.nsISessionStartup.RESUME_SESSION;
  222.   },
  223.  
  224.   /**
  225.    * Get the type of pending session store, if any.
  226.    */
  227.   get sessionType() {
  228.     return this._sessionType;
  229.   },
  230.  
  231. /* ........ Storage API .............. */
  232.  
  233.   /**
  234.    * Reads a session state file into a string and lets
  235.    * observers modify the state before it's being used
  236.    *
  237.    * @param aFile is any nsIFile
  238.    * @returns a session state string
  239.    */
  240.   _readStateFile: function sss_readStateFile(aFile) {
  241.     var stateString = Cc["@mozilla.org/supports-string;1"].
  242.                         createInstance(Ci.nsISupportsString);
  243.     stateString.data = this._readFile(aFile) || "";
  244.  
  245.     Services.obs.notifyObservers(stateString, "sessionstore-state-read", "");
  246.  
  247.     return stateString.data;
  248.   },
  249.  
  250.   /**
  251.    * reads a file into a string
  252.    * @param aFile
  253.    *        nsIFile
  254.    * @returns string
  255.    */
  256.   _readFile: function sss_readFile(aFile) {
  257.     try {
  258.       var stream = Cc["@mozilla.org/network/file-input-stream;1"].
  259.                    createInstance(Ci.nsIFileInputStream);
  260.       stream.init(aFile, 0x01, 0, 0);
  261.       var cvstream = Cc["@mozilla.org/intl/converter-input-stream;1"].
  262.                      createInstance(Ci.nsIConverterInputStream);
  263.  
  264.       var fileSize = stream.available();
  265.       if (fileSize > MAX_FILE_SIZE)
  266.         throw "SessionStartup: sessionstore.js was not processed because it was too large.";
  267.  
  268.       cvstream.init(stream, "UTF-8", fileSize, Ci.nsIConverterInputStream.DEFAULT_REPLACEMENT_CHARACTER);
  269.       var data = {};
  270.       cvstream.readString(fileSize, data);
  271.       var content = data.value;
  272.       cvstream.close();
  273.  
  274.       return content.replace(/\r\n?/g, "\n");
  275.     }
  276.     catch (ex) { Cu.reportError(ex); }
  277.  
  278.     return null;
  279.   },
  280.  
  281.   /* ........ QueryInterface .............. */
  282.   QueryInterface : XPCOMUtils.generateQI([Ci.nsIObserver,
  283.                                           Ci.nsISupportsWeakReference,
  284.                                           Ci.nsISessionStartup]),
  285.   classID:          Components.ID("{ec7a6c20-e081-11da-8ad9-0800200c9a66}"),
  286. };
  287.  
  288. var NSGetFactory = XPCOMUtils.generateNSGetFactory([SessionStartup]);
  289.